package com.wll.design.策略.controller;

import com.wll.design.策略.service.impl.PayServiceImplAnnotation;
import com.wll.design.策略.service.impl.PayServiceImplAware;
import com.wll.design.策略.service.impl.PayServiceImplCommon;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.PathVariable;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;

/**
 * @ClassName: CeLueTestControler.java
 * @author: wanglulu
 * @version: 1.0.0
 * @Description: 策略 设计模式
 * 参考地址
 * https://mp.weixin.qq.com/s/Pb1LoP1Do4y3aL4-4UXk7w
 *
 * 策略模式定义了算法族，分别封装起来，让它们之间可以相互替换，
 * 此模式让算法的变化独立于使用算法的的客户。这个策略模式的定义是不是有点抽象呢？那我们来看点通俗易懂的比喻：
 *
 * 例如： 假设你跟不同性格类型的小姐姐约会，要用不同的策略，有的请电影比较好，
 * 有的则去吃小吃效果不错，有的去逛街买买买最合适。当然，目的都是为了得到小姐姐的芳心，
 * 请看电影、吃小吃、逛街就是不同的策略。
 *
 * 策略模式使用
 * 策略模式怎么使用呢？酱紫实现的：
 *
 * 一个接口或者抽象类，里面两个方法（一个方法匹配类型，一个可替换的逻辑实现方法）
 * 不同策略的差异化实现(就是说，不同策略的实现类)
 * 使用策略模式
 *
 * 如何使用呢？
 * 我们借助spring的生命周期，使用ApplicationContextAware接口，把对用的策略，
 * 初始化到map里面。然后对外提供resolveFile方法即可。
 *
 *
 * 聚合支付 案例
 * 策略模式 + 工厂 + 单例模式
 *
 * @createTime: 2021/11/24 16:47
 */
@RestController
@RequestMapping("/test/")
public class CeLueTestControler {


    @Autowired
    PayServiceImplAnnotation annotationPay;

    @Autowired
    PayServiceImplAware awarePay;

    @Autowired
    PayServiceImplCommon commonPay;

    /**
     * 基于注解 实现
     * 在项目启动时 将各个支付初始化完成 存放在 map 中
     * @param code
     */
    @RequestMapping("pay1/{code}")
    public void annotationPay(@PathVariable String code) {
        annotationPay.toPay(code);
    }


    /**
     * 基于 aware 动态拼接 实现
     * 在需要支付时  动态拼接class  通过 ApplicationContext.gtBean 获取要那种支付实例
     * @param code
     */
    @RequestMapping("pay2/{code}")
    public void awarePay(@PathVariable String code) {
        awarePay.toPay(code);
    }


    /**
     * 常规写法
     * @param code
     */
    @RequestMapping("pay3/{code}")
    public void commonPay(@PathVariable String code) {
        commonPay.toPay(code);
    }

}
